package com.dog.basics.service.sys.impl;


import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.lang.Validator;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.dog.basics.bean.dto.admin.sys.SysUserDto;
import com.dog.basics.bean.dto.admin.sys.SysUserEditDto;
import com.dog.basics.bean.dto.admin.sys.SysUserSaveDto;
import com.dog.basics.bean.model.sys.SysRole;
import com.dog.basics.bean.model.sys.SysUser;
import com.dog.basics.bean.model.sys.SysUserRole;
import com.dog.basics.bean.vo.admin.sys.SysUserPageVo;
import com.dog.basics.common.util.PageParam;
import com.dog.basics.common.util.R;
import com.dog.basics.dao.sys.SysRoleMapper;
import com.dog.basics.dao.sys.SysUserMapper;
import com.dog.basics.dao.sys.SysUserRoleMapper;
import com.dog.basics.service.sys.SysUserService;
import lombok.AllArgsConstructor;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;


/**
 * 系统用户
 *
 * @author dog
 */
@Service("sysUserService")
@AllArgsConstructor
public class SysUserServiceImpl extends ServiceImpl<SysUserMapper, SysUser> implements SysUserService {
    private final SysUserMapper sysUserMapper;
    private final PasswordEncoder passwordEncoder;
    private final SysUserRoleMapper sysUserRoleMapper;
    private final SysRoleMapper sysRoleMapper;

    @Override
    public SysUser getSysUserById(Long userId) {
        return this.getById(userId);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updatePasswordByUserId(Long userId, String newPassword) {
        SysUser user = new SysUser();
        user.setPassword(newPassword);
        user.setUserId(userId);
        this.updateById(user);
    }

    /**
     * 分页的用户条件公用类
     *
     * @param roleId
     * @param userIds
     */
    public List<Long> getRoleUserIdSWhere(Long roleId, List<Long> userIds) {
        List<Long> collect = sysUserRoleMapper.selectList(Wrappers.<SysUserRole>lambdaQuery().eq(SysUserRole::getRoleId, roleId)).stream().map(
                e -> e.getUserId()
        ).collect(Collectors.toList());
        if (CollUtil.isNotEmpty(collect)) {
            userIds = collect;
        } else {
            userIds.add(-2L);
        }
        return userIds;
    }

    @Override
    public IPage<SysUserPageVo> getSysUserPage(PageParam<SysUser> page, SysUserDto dto) {
        // 判断所属角色的用户ID
        List<Long> userIds = CollUtil.newArrayList();
        if (ObjectUtil.isNotEmpty(dto.getRoleId())) {
            userIds = getRoleUserIdSWhere(dto.getRoleId(), userIds);
        }
        // 查询数据
        IPage iPage = this.page(page, Wrappers.<SysUser>lambdaQuery()
                .in(CollUtil.isNotEmpty(userIds), SysUser::getUserId, userIds)
                .ne(SysUser::getUserId, 1L)
                .like(StrUtil.isNotBlank(dto.getUsername()), SysUser::getUsername, dto.getUsername())
                .eq(ObjectUtil.isNotNull(dto.getKindergartenId()), SysUser::getKindergartenId, dto.getKindergartenId())
                .like(StrUtil.isNotBlank(dto.getPhone()), SysUser::getMobile, dto.getPhone())
                .orderByDesc(SysUser::getCreateTime));

        List<SysUser> records = iPage.getRecords();
        iPage.setRecords(records.stream().map(sysUser -> {
            SysUserPageVo sysUserPageVo = new SysUserPageVo();
            BeanUtil.copyProperties(sysUser, sysUserPageVo);
            List<Long> roleIdList = sysUserRoleMapper.selectList(Wrappers.<SysUserRole>lambdaQuery().eq(SysUserRole::getUserId, sysUser.getUserId())).stream().map(e -> e.getRoleId()).collect(Collectors.toList());
            List<SysRole> roleList = sysRoleMapper.selectList(Wrappers.<SysRole>lambdaQuery().in(roleIdList.size() != 0, SysRole::getRoleId, roleIdList));
            List<String> roleNameList = roleList.stream().map(e -> e.getRoleName()).collect(Collectors.toList());
            sysUserPageVo.setRoleIdList(roleIdList);
            sysUserPageVo.setRoleNameList(roleNameList);
            if (CollUtil.isNotEmpty(roleList)) {
                sysUserPageVo.setRemark(roleList.get(0).getRemark());
            }
            return sysUserPageVo;
        }).collect(Collectors.toList()));
        return iPage;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveUserAndUserRole(SysUserSaveDto sysUserSaveDto) {
        Validator.validateTrue(CollUtil.isEmpty(
                this.list(new LambdaQueryWrapper<SysUser>().eq(SysUser::getUsername, sysUserSaveDto.getUsername()))),
                "该用户名已存在");
        Validator.validateTrue(CollUtil.isEmpty(
                this.list(new LambdaQueryWrapper<SysUser>().eq(SysUser::getMobile, sysUserSaveDto.getMobile()))),
                "该手机号已存在");
        SysUser sysUser = new SysUser();
        BeanUtil.copyProperties(sysUserSaveDto, sysUser);
        if (sysUserSaveDto.getRemark().equals("admin")) {
            sysUser.setAccountType(1);
        } else if (sysUserSaveDto.getRemark().equals("agent")) {
            sysUser.setAccountType(2);
        } else {
            sysUser.setAccountType(3);
        }
        sysUser.setPassword(passwordEncoder.encode(sysUser.getPassword()));
        sysUser.setCreateTime(DateUtil.currentSeconds());
        // 判断添加用户是否成功
        Validator.validateTrue(retBool(sysUserMapper.insert(sysUser)), "添加用户出错");
        // 角色不为空添加角色信息
        if (CollUtil.isNotEmpty(sysUser.getRoleIdList())) {
            //保存用户与角色关系
            sysUserRoleMapper.insertUserAndUserRole(sysUser.getUserId(), sysUser.getRoleIdList());
        }
        // 职位不为空添加职位信息
/*		if (CollUtil.isNotEmpty(sysUser.getPosList())) {
			//保存用户与职位关系
			sysUserPosMapper.insertUserAndUserPos(sysUser.getUserId(), sysUser.getPosList());
		}*/
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public R<Boolean> updateUserAndUserRole(SysUserEditDto sysUserEdit) {
        SysUser sysUser = this.getById(sysUserEdit.getUserId());
        SysUser mobile = this.getOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getMobile, sysUserEdit.getMobile()));
        if (sysUser != null && !Objects.equals(sysUser.getUserId(), sysUserEdit.getUserId())) {
            return R.failed("该用户已存在");
        } else if (mobile != null && !Objects.equals(mobile.getUserId(), sysUserEdit.getUserId())) {
            return R.failed("该手机号已存在");
        }

        BeanUtil.copyProperties(sysUserEdit, sysUser);
        if (sysUserEdit.getRemark().equals("admin")) {
            sysUser.setAccountType(1);
        } else if (sysUserEdit.getRemark().equals("agent")) {
            sysUser.setAccountType(2);
        } else {
            sysUser.setAccountType(3);
        }
        // 更新用户
        sysUserMapper.updateById(sysUser);

        //先删除用户与角色关系
        sysUserRoleMapper.deleteByUserId(sysUser.getUserId());

        if (CollUtil.isNotEmpty((sysUser.getRoleIdList()))) {
            //保存用户与角色关系
            sysUserRoleMapper.insertUserAndUserRole(sysUser.getUserId(), sysUser.getRoleIdList());
        }

	/*	//先删除用户与职位关系
		sysUserPosMapper.deleteByUserId(sysUser.getUserId());

		// 职位不为空添加职位信息
		if (CollUtil.isNotEmpty(sysUser.getPosList())) {
			//保存用户与职位关系
			sysUserPosMapper.insertUserAndUserPos(sysUser.getUserId(), sysUser.getPosList());
		}*/
        return R.ok();
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteBatch(Long[] userIds) {
        //删除用户
        sysUserMapper.deleteBatch(userIds);
        //删除用户与角色
        //   sysUserRoleMapper.deleteByUserId(userIds);
        //删除用户与职位
        //sysUserPosMapper.deleteBatchByUserIds(userIds);
    }

    /**
     * 重置密码
     *
     * @param sysUserId
     * @return guonh 2020年2月10日
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean editResetPassword(Long sysUserId) {
        // 查询用户信息是否存在
        SysUser sysUser = this.getById(sysUserId);
        Validator.validateNotNull(sysUser, "用户信息不存在");
        // 执行重置密码
        SysUser editSysUser = new SysUser();
        editSysUser.setUserId(sysUser.getUserId());
        editSysUser.setPassword(passwordEncoder.encode("123456"));
        return this.updateById(editSysUser);
    }

    /**
     * 冻结 - 解封账户
     *
     * @param sysUserId
     * @return guonh 2020年2月10日
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean editFrozenAccounts(Long sysUserId) {
        // 查询用户信息是否存在
        SysUser sysUser = this.getById(sysUserId);
        Validator.validateNotNull(sysUser, "用户信息不存在");
        // 执行冻结 解冻账户
        SysUser editSysUser = new SysUser();
        editSysUser.setUserId(sysUser.getUserId());
        editSysUser.setStatus(Validator.equal(sysUser.getStatus(), 0) ? 1 : 0);
        return this.updateById(editSysUser);
    }
}
